# include "central_cache.h"

namespace memory_pool {
const std::chrono::milliseconds central_cache::DELAY_INTERVAL{1000};
static const size_t SPAN_PAGES = 8;
void* central_cache::fetch_range(size_t index) {
    // 申请内存过大，从大内存池申请
    if (index > FREE_LIST_SIZE) {
        return nullptr;
    }
    // 自旋锁
    while (central_free_list_lock_[index].test_and_set(std::memory_order_acquire)) {
        std::this_thread::yield();
    }
    void* ret = nullptr;
    try{
        ret = central_free_list_[index].load(std::memory_order_relaxed);
        if (!ret) {
            // 从页缓存获取新的内存块
            size_t size = (index + 1) * ALIGNMENT;
            ret = fetch_from_page_cache(size);
            if (!ret) {
                central_free_list_lock_[index].clear(std::memory_order_release);
                return nullptr;
            }
            // 将获取的内存块切分为小块 》 放入链表
            char* ptr = static_cast<char*>(ret);
            // 计算实际从page cache获取的页数
            size_t num_pages = (size <= SPAN_PAGES * page_cache::PAGE_SIZE) ? SPAN_PAGES : (size + page_cache::PAGE_SIZE - 1) / page_cache::PAGE_SIZE;
            // 使用实际页数计算块数
            size_t num_blocks = (num_pages * page_cache::PAGE_SIZE) / size;
            if (num_blocks > 1) {
                for (size_t i = 1; i < num_blocks; ++i) {
                    void* current = ptr + (i - 1) * size;
                    void* next = ptr + i * size;
                    *reinterpret_cast<void**>(current) = next;
                }
                *reinterpret_cast<void**>(ptr + (num_blocks - 1) * size) = nullptr;
                void* next = reinterpret_cast<void*>(ret);
                *reinterpret_cast<void**>(ret) = next;
                central_free_list_[index].store(next, std::memory_order_release);
                size_t trackerIndex = span_tracker_count++;
                if (trackerIndex < span_tracker_array_.size()) {
                    span_tracker_array_[trackerIndex].span_addr.store(ptr, std::memory_order_release);
                    span_tracker_array_[trackerIndex].num_pages.store(num_pages, std::memory_order_release);
                    span_tracker_array_[trackerIndex].block_count.store(num_blocks, std::memory_order_release);
                    span_tracker_array_[trackerIndex].free_count.store(num_blocks - 1, std::memory_order_release);
                }
            }
        } else {
            void* next = *reinterpret_cast<void**>(ret);
            *reinterpret_cast<void**>(ret) = nullptr;
            central_free_list_[index].store(next, std::memory_order_release);
            SpanTracker* tracker = getSpanTracker(ret);
            if (tracker) {
                tracker->free_count.fetch_sub(1, std::memory_order_release);
            }
        }
    } catch (...) {
        central_free_list_lock_[index].clear(std::memory_order_release);
        throw;
    }
    central_free_list_lock_[index].clear(std::memory_order_release);
    return ret;
}
void return_range(void* start, size_t size, size_t index) {
    // 检查入参
    if (!start || size == 0 || index >= FREE_LIST_SIZE) {
        return;
    }
    
}
}